# -*- coding: utf-8 -*-
import web
import os
from string import strip

import config

#Module
from pymongo import MongoClient
client = MongoClient(config.mongourl)
test_db = client[config.dbs_mongo]
user_coll = test_db[config.coll]

#Module for sending email
from email import encoders
from smtplib import SMTP
from email.header import Header
from email.mime.text import MIMEText
from email.utils import parseaddr, formataddr

#Module
import app.controllers

web.config.debug = False
#session = web.session.Session(app, web.session.DiskStore('sessions'), initializer={'count':0})
render = web.template.render('app/views/')
urls = (
        '/', 'welcome',
        '/register', 'register',
        '/reg_result', 'reg_result',
        '/login', 'login',
        '.relogin', 'relogin',
        '/forget_password', 'forget_password',
        '/send_link', 'send_link',
        '/reset_page', 'reset_page',
        '/reset_password', 'reset_password',
        '/return_to_login', 'return_to_login',
        '/user_center','user_center',
        '/research',  'research',
        '/code', 'code',
        '/service', 'service',

        '/settings',                                 'app.controllers.settings.index',
        '/settings/change_nickname',                 'app.controllers.settings.change_nickname',
        '/settings/change_password',                 'app.controllers.settings.change_password',
        '/settings/change_email',                    'app.controllers.settings.change_email',

        '/(|new|all|admitted)', 'app.controllers.browse.list',
        '/applicant/(\d+)', 'app.controllers.browse.show',
        )
#=======================================================
# This function is used to create the code from the user
#=======================================================
def create_file(file1, file2):
    file_origin = open(file1, "r")
    content = file_origin.read()
    content_add = ""
    pos = content.find("#insert above")

    #if the code is not written in the file 'file2', then pass.
    if os.path.getsize(file2) == 0:
        content = content[:pos] + "    pass\n" + content[pos:]
    else:
        file_add = open(file2, "r")
        while 1:
            line = file_add.readline()
            if not line:
                break
            new_line = "    " + line.rstrip() + '\n'
            content_add = content_add + new_line
        content = content[:pos] + content_add + content[pos:]
        file_add.close()

    file_origin = open("./new_sim.py", "w")
    file_origin.write(content)
    file_origin.close()

def write_data(data):
    output_file = open('output.py', 'wb')
    output_file.write(data)
    output_file.close()

def verification(phonenumber, key):
    return (test_db.user_coll.find({"user_phone": phonenumber, "user_md5": key}).count() == 1)

def md5(pwd):
    import hashlib
    m = hashlib.md5()
    m.update(pwd)
    return m.hexdigest()

#For sending email
def _format_addr(s):
    name, addr = parseaddr(s)
    return formataddr(( \
        Header(name, 'utf-8').encode(), \
        addr.encode('utf-8') if isinstance(addr, unicode) else addr))

def send_email(SMTP_host, from_addr, password, to_addrs, subject, content):
    from_addr = raw_input('From: ')
    password = raw_input('Password: ')
    to_addr = raw_input('To: ')
    smtp_server = raw_input('SMTP server: ')

    email_client = SMTP(SMTP_host)
    email_client.login(from_addr, password)
    # create msg
    msg = MIMEText('<html><body><h1>Hello</h1>' +
                '<p>send by <a href="http://www.python.org">Python</a>...</p>' +
                    '</body></html>', 'html', 'utf-8')
    #msg = MIMEText(content, 'html', 'utf-8')
    msg['Subject'] = Header(subject, 'utf-8')
    msg['From'] = _format_addr(u'AI智客 <%s>' % from_addr)
    #msg['From'] = 'main<530419350@qq.com>'
    #msg['To'] = 'huanggang08@163.com'
    msg['To'] = _format_addr(u'用户 <%s>' % to_addr)
    email_client.sendmail(from_addr, to_addrs, msg.as_string())
    email_client.quit
    print ('sending email......success!')

class count:
    def GET(self):
        session.count += 1
        return str(session.count)

class reset:
    def GET(self):
        session.kill()
        return ""

class this_user(object):
    def __init__(self, phonenumber, username, md5):
        self.pn = phonenumber
        self.un = username
        self.md5 = md5

class welcome:
    def GET(self):
        return render.welcome()
        #i = web.input(name=None)
        #record = test_db.user_coll.find({"user_id":"sai"})
        #username = record['user_id']
        #username = 'Hello world!'
        #return "hello world"
        #return record

#===================================================
#In the class 'register', after the user input the data,and push "confirm" button,
#all data will be inserted into the database.
#Similar parts: the 'comment' class;
#===================================================
class register:
    def GET(self):
        return render.register()

class service:
    def GET(self):
        #raise web.seeother('/service')
        return service()

class reg_result:
    def POST(self):
        user_info = web.input()
        phonenumber = user_info['phonenumber']
        password = user_info['password']
        username = user_info['username']
        md5_pn = md5(phonenumber)
        md5_pw = md5(password)
        md5_f = md5(md5_pn + md5_pw)
        #If the username is already exist, the reg. fails.
        if (test_db.user_coll.find({"user_id":username}).count() == 1):
            return render.reg_fail()
        else:
            u = test_db.user_coll.insert_one(
                {"user_id": username,
                 "user_phone": phonenumber,
                 "user_md5": md5_f,
                 }
                )
            return render.reg_success()
class login:
    def POST(self):
        a = []
        user_input = web.input()
        md5_pn = md5(user_input['phonenumber'])
        md5_pw = md5(user_input['password'])
        md5_f = md5(md5_pn + md5_pw)
        if (verification(user_input['phonenumber'], md5_f)):
            cursor = test_db.user_coll.find({"user_phone": user_input['phonenumber']})
            for username in cursor:
                a.append(username["user_id"])
            user = this_user(user_input['phonenumber'], a[0], md5_f,)
            return render.user_center()
        else:
            return render.relogin()

class relogin:
    def POST(self):
        a = []
        user_input = web.input()
        md5_pn = md5(user_input['phonenumber'])
        md5_pw = md5(user_input['password'])
        md5_f = md5(md5_pn + md5_pw)
        if (verification(user_input['phonenumber'], md5_f)):
            cursor = test_db.user_coll.find({"user_phone": user_input['phonenumber']})
            for username in cursor:
                a.append(username["user_id"])
            user = this_user(user_input['phonenumber'], a[0], md5_f)
            return render.user_center()
        else:
            return render.relogin()

class forget_password:
    def GET(self):
        return render.forget_password()

class send_link:
    def POST(self):
        user_input = web.input()
        email = user_input['email']
        verification = user_input['verification']
        # 输入验证码
        host = 'smtp.163.com'
        from_addr = 'gang.huang@capital.cn'
        password = '9861108xt'
        #to_addr = email
        to_addr = '530419350@qq.com'
        subject = '请点击以下链接进行密码重置'
        content = """
        <p><a href="http://0.0.0.0:8080/reset_page">请点击此链接进行密码修改</a></p>
        """
        send_email(host, from_addr, password, to_addr, subject, content)
        return render.send_link()

class reset_page:
    def GET(self):
        return render.reset_page()

class reset_password:
    def POST(self):
        a = []
        user_input = web.input()
        username = user_input['username']
        password = user_input['password']
        if (test_db.user_coll.find({"user_id":username}).count() == 0):
            return render.reset_fail()
        else:
            cursor = test_db.user_coll.find({"user_id":username})
            for c in cursor:
                a.append(c["user_phone"])
            phonenumber = a[0]
            md5_pn = md5(phonenumber)
            md5_pw = md5(password)
            md5_f = md5(md5_pn + md5_pw)
            u = test_db.user_coll.update({"user_phone" : phonenumber},{"$set": {"user_md5" : md5_f}})
            return render.reset_password()

#After pushing the "confirm" button, go to the page '/'.
#Use POST() method, instead of GET()
#Added 2017-08-31
class return_to_login:
    def POST(self):
        raise web.seeother('/')

class user_center:
    def POST(self):
        return render.user_center()

class research:
    def POST(self):
        return render.research()

class code:
    def POST(self):
        user_input = web.input()
        code = user_input['code']
        write_data(code)
        create_file("test.py", "output.py")
        print ("code output:")
        a = os.popen('python ./new_sim.py')
        print (a.read())
        #os.remove('./new_sim.py')
        #将new_sim.py生成docker镜像在容器运行，生成结果，返回给前端

        return render.code()

if __name__ == "__main__":
    app = web.application(urls, globals())
    app.run()
